# encoding: utf-8
import json, datetime

from app.extensions import log, db
from flask_restplus import Resource
from app.extensions.api import Namespace
from app.modules.common.utils import DbCommit, strToList, ComplexEncoder
from . import parameters, schemas
from .models import ProdSchemaDefine, ProdTableDefine, ProdTableExport, ProdTableClean, ProdTableCheckRows, \
    ProdTableInit
from app.modules.common.mailUtil import sendMail

api = Namespace('prod', description = "prod")  # pylint: disable=invalid-name


@api.route('/schema')
class Schema(Resource):
    @api.parameters(parameters.Parameters())
    @api.response(schemas.SchemaListSchema(many = False))
    def get(self, args, **kwargs):
        """
        获取数据库列表
        :param args:
        :return:
        """
        log.info("start get schema list ")
        _list = ProdSchemaDefine.query.filter_by(is_ignore = 'N').all()
        return {'success': True, 'msg': '', 'data': _list}


@api.route('/table')
class Table(Resource):
    @api.parameters(parameters.TableGetParameters())
    @api.response(schemas.TableListSchema(many = False))
    def get(self, args, **kwargs):
        """
        获取数据库下表列表
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        tableName = args['tableName']
        log.info("start get schema talbe list . schemaName is %s " % schemaName)
        log.info("start get schema talbe list . tableName is %s " % tableName)
        _query = ProdTableDefine.query.filter_by(table_schema = schemaName).filter_by(is_ignore = 'N')
        if tableName is not None:
            _query = _query.filter_by(table_name = tableName)
        _list = _query.all()
        return {'success': True, 'msg': '', 'data': _list}


@api.route('/table/checkrow')
class Table(Resource):
    @api.parameters(parameters.TableCheckrowGetParameters())
    @api.response(schemas.BaseSchema(many = False))
    def get(self, args, **kwargs):
        """
        修改表的isCheckRows
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        tableName = args['tableName']
        isCheckRows = args['isCheckRows']
        isNeedClean = args['isNeedClean']
        log.info("start update talbe isCheckRows . schemaName is %s " % schemaName)
        log.info("start update talbe isCheckRows . tableName is %s " % tableName)
        log.info("start update talbe isCheckRows . isCheckRows is %s " % isCheckRows)
        log.info("start update talbe isCheckRows . isNeedClean is %s " % isNeedClean)
        _info = ProdTableDefine.query.filter_by(table_schema = schemaName).filter_by(table_name = tableName).first()
        if _info is None:
            _msg = "查询表记录为空"
            log.error("============== %s ==============" % _msg)
            return {'success': False, 'msg': _msg}

        if isCheckRows is not None:
            _info.is_check_rows = isCheckRows
        if isNeedClean is not None:
            _info.is_need_clean = isNeedClean
        return DbCommit()


@api.route('/list')
class List(Resource):
    @api.parameters(parameters.ListGetParameters())
    @api.response(schemas.ViewListSchema(many = False))
    def get(self, args, **kwargs):
        """
        查询维护信息列表
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        log.info("start get list . schemaName is %s " % schemaName)
        _result = db.session.execute(
            "SELECT * FROM v_prod_table_maintenance where table_schema = :table_schema",
            {'table_schema': schemaName})
        _list = []
        for row in _result:
            _r = json.loads(json.dumps(dict(row), encoding = "UTF-8", ensure_ascii = False, cls = ComplexEncoder))
            _list.append(_r)
        return {'success': True, 'msg': '', 'data': _list}


@api.route('/export')
class Export(Resource):
    @api.parameters(parameters.ExportGetParameters())
    @api.response(schemas.ExportListSchema(many = False))
    def get(self, args, **kwargs):
        """
        查询导出规则
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        tableName = args['tableName']
        log.info("start get export . schemaName is %s " % schemaName)
        log.info("start get export . tableName is %s " % tableName)

        _query = ProdTableExport.query.filter_by(table_schema = schemaName).filter_by(
            table_name = tableName).filter_by(
            env_type = 'DEVTEST').all()

        return {'success': True, 'msg': '', 'data': _query}

    @api.parameters(parameters.ExportPostParameters())
    @api.response(schemas.BaseSchema(many = False))
    def post(self, args, **kwargs):
        """
        维护导出规则
        :param args:
        :return:
        """
        schemaName = args['table_schema']
        tableName = args['table_name']
        type = args['env_type']
        script = args['script']
        remark = args['remark']
        updatedby = args['updatedby']
        log.info("start update export . schemaName is %s " % schemaName)
        log.info("start update export . tableName is %s " % tableName)
        log.info("start update export . type is %s " % type)
        log.info("start update export . script is %s " % script)
        log.info("start update export . remark is %s " % remark)
        log.info("start update export . updatedby is %s " % updatedby)
        # 判断是否存在记录
        _export = ProdTableExport.query.filter_by(table_schema = schemaName).filter_by(
            table_name = tableName).filter_by(
            env_type = type).first()
        if _export is None:
            _export = ProdTableExport(table_schema = schemaName, table_name = tableName, env_type = type,
                                      script = script, remark = remark, created = datetime.datetime.now(),
                                      createdby = updatedby, updated = datetime.datetime.now(), updatedby = updatedby)
            db.session.add(_export)
        else:
            _export.script = script
            _export.remark = remark
            _export.updated = datetime.datetime.now()
            _export.updatedby = updatedby
        return DbCommit()


@api.route('/clean')
class Clean(Resource):
    @api.parameters(parameters.ExportGetParameters())
    @api.response(schemas.CleanListSchema(many = False))
    def get(self, args, **kwargs):
        """
        查询清洗条件
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        tableName = args['tableName']
        log.info("start get clean . schemaName is %s " % schemaName)
        log.info("start get clean . tableName is %s " % tableName)

        _query = ProdTableClean.query.filter_by(table_schema = schemaName).filter_by(
            table_name = tableName).order_by(ProdTableClean.is_active.desc(), ProdTableClean.sort.asc()).all()

        return {'success': True, 'msg': '', 'data': _query}

    @api.parameters(parameters.CleanPostParameters())
    @api.response(schemas.BaseSchema(many = False))
    def post(self, args, **kwargs):
        """
        维护导出规则
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        tableName = args['tableName']
        _list = strToList(args['list'])
        log.info("start update export . schemaName is %s " % schemaName)
        log.info("start update export . tableName is %s " % tableName)
        log.info("start update export . list is %s " % _list)

        if type(_list) is not list:
            _msg = "this list %s is not list" % _list
            log.error("============== %s ==============" % _msg)
            return {'success': False, 'msg': _msg}

        for _export in _list:
            if _export['id'] is None or _export['id'] == '':
                # 新增记录
                _clean = ProdTableClean(table_schema = schemaName, table_name = tableName, script = _export['script'],
                                        remark = _export['remark'], is_active = _export['is_active'],
                                        sort = _export['sort'], created = datetime.datetime.now(),
                                        createdby = _export['createdby'])
                db.session.add(_clean)
            else:
                # 修改记录
                _clean = ProdTableClean.query.filter_by(id = _export['id']).first()
                if _clean is None:
                    _msg = "记录%s不存在" % _export['id']
                    log.error("============== %s ==============" % _msg)
                else:
                    _clean.script = _export['script']
                    _clean.remark = _export['remark']
                    _clean.sort = _export['sort']
                    _clean.is_active = _export['is_active']
                    _clean.updated = datetime.datetime.now()
                    _clean.updatedby = _export['updatedby']

        return DbCommit()


@api.route('/checkRow')
class CheckRow(Resource):
    @api.parameters(parameters.ExportGetParameters())
    @api.response(schemas.CheckRowSchema(many = False))
    def get(self, args, **kwargs):
        """
        查询行确认
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        tableName = args['tableName']
        log.info("start check row . schemaName is %s " % schemaName)
        log.info("start check row . tableName is %s " % tableName)

        _query = ProdTableCheckRows.query.filter_by(table_schema = schemaName).filter_by(
            table_name = tableName).first()

        if _query is None:
            _msg = "数据库%s 表%s 记录不存在" % (schemaName, tableName)
            log.error("============== %s ==============" % _msg)
            return {'success': False, 'msg': _msg}
        return {'success': True, 'msg': '', 'data': _query}

    @api.parameters(parameters.CheckRowPostParameters())
    @api.response(schemas.BaseSchema(many = False))
    def post(self, args, **kwargs):
        """
        确认行
        :param args:
        :return:
        """
        id = args['id']
        schemaName = args['table_schema']
        tableName = args['table_name']
        checkedby = args['checkedby']
        thisRows = args['this_rows']
        checkedRows = args['checked_rows']
        remark = args['remark']
        log.info("start check row . id is %s " % id)
        log.info("start check row . schemaName is %s " % schemaName)
        log.info("start check row . tableName is %s " % tableName)
        log.info("start check row . checkedby is %s " % checkedby)
        log.info("start check row . thisRows is %s " % thisRows)
        log.info("start check row . checkedRows is %s " % checkedRows)
        log.info("start check row . remark is %s " % remark)

        _check = ProdTableCheckRows.query.filter_by(id = id).first()
        if _check is None:
            _check = ProdTableCheckRows(table_schema = schemaName, table_name = tableName, this_rows = thisRows,
                                        checked_rows = checkedRows, checked_date = datetime.datetime.now(),
                                        checkedby = checkedby, remark = remark)
            db.session.add(_check)
        else:
            _check.this_rows = thisRows
            _check.checked_rows = checkedRows
            _check.checked_date = datetime.datetime.now()
            _check.checkedby = checkedby
            _check.remark = remark

        return DbCommit()


@api.route('/init')
class Init(Resource):
    @api.parameters(parameters.InitGetParameters())
    @api.response(schemas.InitListSchema(many = False))
    def get(self, args, **kwargs):
        """
        查询初始化条件
        :param args:
        :return:
        """
        schemaName = args['schemaName']
        envType = args['envType']
        log.info("start query init . schemaName is %s " % schemaName)
        log.info("start query init . envType is %s " % envType)

        _query = ProdTableInit.query.filter_by(table_schema = schemaName)
        if envType is not None:
            _query = _query.filter_by(env_type = envType)

        _list = _query.order_by(ProdTableInit.is_active.desc()).all()

        return {'success': True, 'msg': '', 'data': _list}

    @api.parameters(parameters.InitPostParameters())
    @api.response(schemas.BaseSchema(many = False))
    def post(self, args, **kwargs):
        """
        维护初始化条件
        :param args:
        :return:
        """
        id = args['id']
        schemaName = args['table_schema']
        instanceName = args['table_schema_instance']
        envType = args['env_type']
        script = args['script']
        remark = args['remark']
        isActive = args['is_active']
        updatedby = args['updatedby']
        log.info("start update init . id is %s " % id)
        log.info("start update init . schemaName is %s " % schemaName)
        log.info("start update init . instanceName is %s " % instanceName)
        log.info("start update init . envType is %s " % envType)
        log.info("start update init . script is %s " % script)
        log.info("start update init . remark is %s " % remark)
        log.info("start update init . isActive is %s " % isActive)
        log.info("start update init . updatedby is %s " % updatedby)

        if id is None:
            # 新增
            _init = ProdTableInit(table_schema = schemaName, table_schema_instance = instanceName, env_type = envType,
                                  script = script, remark = remark, is_active = isActive,
                                  created = datetime.datetime.now(), createdby = updatedby)
            db.session.add(_init)
        else:
            _init = ProdTableInit.query.filter_by(id = id).first()
            if _init is None:
                _msg = "记录%s不存在" % id
                log.error("============== %s ==============" % _msg)
                return {'success': False, 'msg': _msg}
            else:
                _init.table_schema_instance = instanceName
                _init.script = script
                _init.remark = remark
                _init.is_active = isActive
                _init.updated = datetime.datetime.now()
                _init.updatedby = updatedby
        return DbCommit()


@api.route('/dbProdReport')
class dbProdReport(Resource):
    @api.parameters(parameters.Parameters())
    @api.response(schemas.BaseSchema(many = False))
    def get(self, args, **kwargs):
        """
        获取数据库列表
        :param args:
        :return:
        """
        log.info("app.modules.prod.resources.dbProdReport start ")
        dbProdReport()
        return {'success': True, 'msg': ''}


def dbProdReport():
    _result = db.session.execute("SELECT * FROM v_prod_table_maintenance_monitor")
    for row in _result:
        _r = json.loads(json.dumps(dict(row), encoding = "UTF-8", ensure_ascii = False, cls = ComplexEncoder))
        sendMail(
            _to = '%s,it_helpdesk@winit.com.cn,lunan.xu@winit.com.cn,tongsan.chen@winit.com.cn,min.wan@winit.com.cn' %
                  _r['manager'], _subject = _r['title'],
            _body = _r['content'])
